+SPIP-Core spip-3.2.4 -> spip-3.2.5 16 septembre 2019
+-------------------------------------------------------------
+r24283 | ben | (lun. 08 avril 2019) | SPIP 3.2.4
+r24289 | Cerdic | (lun. 08 avril 2019) | Permettre de personaliser le _HEADER_VARY, ce qui peut etre necessaire pour le reverse proxy en amont du frontal
+r24306 | Cerdic | (jeu. 09 mai 2019) | Support des images SVG : |balise_img ne cherche pas a calculer une width/height dans ce cas et |balise_svg permet d'inserer le SVG inline avec ou sans alt selon les bonnes pratiques de http://www.accede-web.com/notices/html-css-javascript/6-images-icones/6-2-svg-images-vectorielles/
+r24314 | Cerdic | (ven. 31 mai 2019) | Fix : la class filtre_inactif etait inactive si en premiere position de l'attribut class
+r24319 | marcimat| (mer. 12 juin 2019) | Report de 52d55876e : Petite notice PHP en moins parfois avec une boucle data.
+r24322 | marcimat| (jeu. 04 juil. 2019) | Report de r24321 : Ticket #4351 : utiliser de préférence l’email pour préremplir le formulaire de login lorsque c’est possible.
+r24325 | marcimat| (mar. 16 juil. 2019) | [report de 5749e10f0b] (Warning en PHP 7.2) Éviter une notice PHP lorsque deux plugins de même préfixes sont affichés (sans SVP).
+r24380 | Cerdic | (lun. 26 août 2019) | Rewording sur le message de succes eventuel apres envoi d'un email de reset mot de passe
+r24381 | Cerdic | (lun. 26 août 2019) | ne rien laisser passer dans var_erreur, c'est encore plus sur et de toute facon on attends pas de HTML ici (Boulouiz Youssouf)
+r24382 | Cerdic | (lun. 26 août 2019) | Fix menu 2 col pour ne pas avoir un lien coupe en 2 par le changement de colonne
+r24392 | cedric | (dim. 15 sept. 2019) | perf issue : eviter d'inclure plein de fichier quand on appelle _T() sans argument
+r24397 | cedric | (lun. 16 sept. 2019) | sanitizer les URLs de redirection au cas ou (beaucoup de conditions pour arriver la et que ce soit effectivement nocif, mais bon)
+r24398 | cedric | (lun. 16 sept. 2019) | centraliser les tests identiques c'est plus simple a mainteanir
+r24399 | cedric | (lun. 16 sept. 2019) | Mise a jour de l'ecran de securite
+
+SPIP-plugins-dist spip-3.2.4 -> spip-3.2.5 16 septembre 2019
+-------------------------------------------------------------
+
+r113884 | cedric | (mar. 12 févr. 2019) | Report de r113883 : une indirection manquante signalee dans https://core.spip.net/issues/4282 (JLuc)
+r114014 | cedric | (ven. 22 févr. 2019) | Report de r114013 : Envoyer des mails en from d'un inconnu c'est de l'usurpation d'identite et ca peut vous conduire au commissariat, en plus d'etre vu comme un SPAM par beaucoup de fournisseur de mail. On laisse donc le from par defaut du site, mais un mets un Reply-To a l'envoyeur et l'email de l'envoyeur suppose (mais pas verifie) en signature du message. C'est plus robuste et moins sujet a litige
+r114612 | bruno | (ven. 22 mars 2019) | report à l'arrache de r114572 pour sauver les stats de tonton sur plugin.spip :)
+r114613 | eric | (ven. 22 mars 2019) | Il manquait la mise à jour de la fonction svp_compter qui était dans un commit précédent à celui qui a été mergé.
+r114666 | bruno | (jeu. 28 mars 2019) | version 2.1.8 : report de r114665ne pas afficher le lien "Modifier" au survol si pas autorisé fix #4307
+r114855 | marcimat | (lun. 08 avril 2019) | Report de r112276 : Fix #4205 : À l’installation, il n’y a pas encore de fichier de sauvegarde des actions SVP. Du coup, il pouvait y avoir un petit bug en tentant de les lire.(Francky).
+r114856 | marcimat | (lun. 08 avril 2019) | Report de r112275 : Ticket #4205 : Compatibilité PHP 7.3. La librairie PCRE passe en v2, et est moins tolérante.Le caractère -, indiqué dans un bloc de caractères `[ - ]`, pour ne pas être pris pour une déclaration d’intervalle (comme `[a-z]`), doit être soit échappé avec \ soit être en tête ou en fin de la structure.(Francky)
+r114857 | marcimat | (lun. 08 avril 2019) | Petite version suite aux reports r114855 et r114856
+r115009 | rasta | (mer. 17 avril 2019) | Report dans la dernière stable de [115008] : Cela fait plus de 8 ans que SPIP dit au gens de se connecter avec leur email dans la notif d'inscription. Et là dans le formulaire de changement de mot de passe, on continuait de leur afficher leur login, dont ils n'avaient jamais entendu parler… On corrige ça, en leur rappelant en priorité l'email s'il existe, et seulement sinon le login.
+r115011 | rasta | (mer. 17 avril 2019) | Backport [115010] : Correction de la correction : dire aux gens d'utiliser leur login aussi si leur email est déjà utilisé par quelqu'un d'autre, que ce soit dans un champ email ou login (Cédric).
+r115017 | rasta | (jeu. 18 avril 2019) | Backport de [115016] : Stupéfaction : dans le where de notre API SQL, lorsque c'est un tableau, ça joint les critères avec un AND mais SANS les sécuriser avec des parenthèses svn st! Du coup si dans un élément on a des OR ça pète tout. Faut mettre les parenthèses soi-même.
+r115053 | real3t | (ven. 26 avril 2019) | Report en 3.2 de r113960 (fixes #4160) : Application du patch proposé ici : https://core.spip.net/issues/4160#change-14773 : Les rangs (numéros de titre) des mots clefs ne sont pas affichés dans les listes déroulantes permettant de les affecter à des articles, rubriques... et autres objets.Retour de la fonctionnalité présente en SPIP 2.1 et perdue en 3.0
+r115213 | jluc | (ven. 03 mai 2019) | report de 115189 pour SPIP 3.2 (#4325 détection sqlite)
+r115621 | rasta | (mer. 12 juin 2019) | roh il manquait un morceau dans le backport en 3.2
+r115800 | bruno | (jeu. 27 juin 2019) | report de r115799
+r116219 | eric | (dim. 04 août 2019) | Report de 116217.Ajout de l'id du commit GIT pour le flux atom Github
+r116220 | eric | (dim. 04 août 2019) | Oups oubli de up de z
+r117846 | cedric | (sam. 14 sept. 2019) | Update CSSTidy v1.6.5 (compat PHP 7.3)
+
SPIP-Core spip-3.2.3 -> spip-3.2.4 08 avril 2019
-------------------------------------------------------------
* ------------------
*/
-define('_ECRAN_SECURITE', '1.3.11'); // 2019-04-08
+define('_ECRAN_SECURITE', '1.3.12'); // 2019-09-16
/*
* Documentation : http://www.spip.net/fr_article4200.html
and $_REQUEST['reinstall'] == 'oui')
$ecran_securite_raison = 'reinstall=oui';
+/*
+ * Pas d'action pendant l'install
+ */
+if (isset($_REQUEST['exec']) and $_REQUEST['exec'] === 'install' and isset($_REQUEST['action'])) {
+ $ecran_securite_raison = 'install&action impossibles';
+}
+
/*
* Échappement xss referer
*/
$_SERVER['HTTP_X_FORWARDED_HOST'] = strtr($_SERVER['HTTP_X_FORWARDED_HOST'], "<>?\"\{\}\$'` \r\n", '____________');
+/*
+ * Pas d'erreur dans l'erreur
+ */
+if (isset($_REQUEST['var_erreur']) and isset($_REQUEST['page']) and $_REQUEST['page'] === 'login') {
+ if (strlen($_REQUEST['var_erreur']) !== strcspn($_REQUEST['var_erreur'], '<>'))
+ $ecran_securite_raison = 'var_erreur incorrecte';
+}
+
+
/*
* Réinjection des clés en html dans l'admin r19561
*/
* Classe CSS éventuelle
* @param string|array $debug
* Informations sur la page contenant une erreur de compilation
- * @return array
+ * @return array|string
* Liste : Chemin du squelette, durée du cache, contexte
**/
function balise_FORMULAIRE_ADMIN_dyn($float = '', $debug = '') {
static $dejafait = false;
- if (!@$_COOKIE['spip_admin']) {
+ if (empty($_COOKIE['spip_admin'])) {
return '';
}
* Code de langue
**/
function admin_lang() {
- $alang = sql_getfetsel('lang', 'spip_auteurs',
- "login=" . sql_quote(preg_replace(',^@,', '', @$_COOKIE['spip_admin'])));
+ $alang = '';
+ if (!empty($_COOKIE['spip_admin'])) {
+ $email_or_login = preg_replace(',^@,', '', $_COOKIE['spip_admin']);
+ $alang = sql_getfetsel('lang', 'spip_auteurs', "email=" . sql_quote($email_or_login));
+ if (!$alang) {
+ $alang = sql_getfetsel('lang', 'spip_auteurs', "login=" . sql_quote($email_or_login));
+ }
+ }
if (!$alang) {
return '';
}
foreach ($tags as $tag) {
$class = extraire_attribut($tag[3], 'class');
if (!$class or
- (strpos($class, 'filtre_inactif') == false
+ (strpos($class, 'filtre_inactif') === false
// compat historique a virer en 3.2
and strpos($class, 'no_image_filtrer') === false)
) {
if (!isset($options['chemin_image']) or $options['chemin_image'] == true) {
$img = chemin_image($img);
}
- if (stripos($atts, 'width') === false) {
+ if (stripos($atts, 'width') === false && !preg_match(',\.svg$,', $img)) {
// utiliser directement l'info de taille presente dans le nom
if ((!isset($options['utiliser_suffixe_size']) or $options['utiliser_suffixe_size'] == true)
and preg_match(',-([0-9]+)[.](png|gif)$,', $img, $regs)
}
+/**
+ * Inserer un svg inline
+ * http://www.accede-web.com/notices/html-css-javascript/6-images-icones/6-2-svg-images-vectorielles/
+ *
+ * pour l'inserer avec une balise <img>, utiliser le filtre |balise_img
+ *
+ * @param string $img
+ * @param string $alt
+ * @param string $class
+ * @return string
+ */
+function filtre_balise_svg_dist($img, $alt = "", $class = "") {
+ if (!$file = find_in_path($img)
+ or !$svg = file_get_contents($file)) {
+ return '';
+ }
+
+ if (!preg_match(",<svg\b[^>]*>,UimsS", $svg, $match)) {
+ return '';
+ }
+ $balise_svg = $match[0];
+ $balise_svg_source = $balise_svg;
+ // IE est toujours mon ami
+ $balise_svg = inserer_attribut($balise_svg, 'focusable', 'false');
+ if ($class) {
+ $balise_svg = inserer_attribut($balise_svg, 'class', $class);
+ }
+ if ($alt){
+ $balise_svg = inserer_attribut($balise_svg, 'role', 'img');
+ $id = "img-svg-title-" . substr(md5("$file:$svg:$alt"),0,4);
+ $balise_svg = inserer_attribut($balise_svg, 'aria-labelledby', $id);
+ $title = "<title id=\"$id\">" . entites_html($alt)."</title>\n";
+ $balise_svg .= $title;
+ }
+ else {
+ $balise_svg = inserer_attribut($balise_svg, 'aria-hidden', 'true');
+ }
+ $svg = str_replace($balise_svg_source, $balise_svg, $svg);
+
+ return $svg;
+}
+
+
+
/**
* Affiche chaque valeur d'un tableau associatif en utilisant un modèle
*
// ne pas laisser passer n'importe quoi dans l'url
$url = str_replace(array('<', '"'), array('<', '"'), $url);
+ $url = str_replace(array("\r", "\n", ' '), array('%0D', '%0A', '%20'), $url);
+ while (strpos($url, '%0A') !== false) {
+ $url = str_replace('%0A', '', $url);
+ }
// interdire les url inline avec des pseudo-protocoles :
if (
(preg_match(",data:,i", $url) and preg_match("/base64\s*,/i", $url))
// en cas d'install ne pas faire confiance au meta_cache eventuel
$cache = cache_meta($table);
- if ((_request('exec') !== 'install' or !test_espace_prive())
+ if ((!$exec = _request('exec') or !autoriser_sans_cookie($exec))
and $new = jeune_fichier($cache, _META_CACHE_TIME)
and lire_fichier_securise($cache, $meta)
and $meta = @unserialize($meta)
function _action_auteur($action, $id_auteur, $pass, $alea) {
static $sha = array();
if (!isset($sha[$id_auteur . $pass . $alea])) {
- if (!isset($GLOBALS['meta'][$alea]) and _request('exec') !== 'install') {
- include_spip('inc/acces');
- charger_aleas();
- if (empty($GLOBALS['meta'][$alea])) {
- include_spip('inc/minipres');
- echo minipres();
- spip_log("$alea indisponible");
- exit;
+ if (!isset($GLOBALS['meta'][$alea])) {
+ if (!$exec = _request('exec') or !autoriser_sans_cookie($exec)){
+ include_spip('inc/acces');
+ charger_aleas();
+ if (empty($GLOBALS['meta'][$alea])){
+ include_spip('inc/minipres');
+ echo minipres();
+ spip_log("$alea indisponible");
+ exit;
+ }
}
}
include_spip('auth/sha256.inc');
include_spip('inc/autoriser');
}
if (autoriser('ecrire','','',$auteur) and _DUREE_COOKIE_ADMIN) {
- spip_setcookie('spip_admin', '@' . $auteur['login'], time() + max(_DUREE_COOKIE_ADMIN, $duree));
+ spip_setcookie('spip_admin', '@' . ($auteur['email'] ?: $auteur['login']), time() + max(_DUREE_COOKIE_ADMIN, $duree));
} // sinon le supprimer ...
else {
spip_setcookie('spip_admin', '', 1);
$options = $defaut_options;
}
- if (is_array($args)) {
+ if (is_array($args) and count($args)) {
if (!function_exists('interdire_scripts')) {
include_spip('inc/texte');
}
/**
* Prédicat sur les scripts de ecrire qui n'authentifient pas par cookie
+ * et beneficient d'une exception
+ *
* @param string $nom
+ * @param bool $strict
* @return bool
*/
-function autoriser_sans_cookie($nom) {
+function autoriser_sans_cookie($nom, $strict = false) {
static $autsanscookie = array('install', 'base_repair');
- $nom = preg_replace('/.php[3]?$/', '', basename($nom));
- return in_array($nom, $autsanscookie);
+ if (in_array($nom, $autsanscookie)) {
+ if (test_espace_prive()){
+ include_spip('base/connect_sql');
+ if (!$strict or !spip_connect()){
+ return true;
+ }
+ }
+ }
+ return false;
}
/**
// pour specifier les versions de SPIP necessaires
// il faut s'en tenir a un nombre de decimales fixe
// ex : 2.0.0, 2.0.0-dev, 2.0.0-beta, 2.0.0-beta2
-$spip_version_branche = "3.2.4";
+$spip_version_branche = "3.2.5";
// cette version dev accepte tous les plugins compatible avec la version ci-dessous
// a supprimer en phase beta/rc/release
#define('_DEV_VERSION_SPIP_COMPAT',"3.1.3");
define('_HEADER_COMPOSED_BY', "Composed-By: SPIP");
}
if (!headers_sent() and _HEADER_COMPOSED_BY) {
- header("Vary: Cookie, Accept-Encoding");
+ if (!defined('_HEADER_VARY')) {
+ define('_HEADER_VARY', "Vary: Cookie, Accept-Encoding");
+ }
+ if (_HEADER_VARY) {
+ header(_HEADER_VARY);
+ }
if (!isset($GLOBALS['spip_header_silencieux']) or !$GLOBALS['spip_header_silencieux']) {
include_spip('inc/filtres_mini');
header(_HEADER_COMPOSED_BY . " $spip_version_affichee @ www.spip.net + " . url_absolue(_DIR_VAR . "config.txt"));
// Les scripts d'insallation n'authentifient pas, forcement,
// alors il faut blinder les variables d'URL
//
-if (autoriser_sans_cookie($exec)) {
+if (autoriser_sans_cookie($exec, false)) {
if (!isset($reinstall)) {
$reinstall = 'non';
}
if (_request('action') or _request('var_ajax') or _request('formulaire_action')) {
- // Charger l'aiguilleur qui va mettre sur la bonne voie les traitements derogatoires
- include_spip('public/aiguiller');
- if (
- // cas des appels actions ?action=xxx
- traiter_appels_actions()
- or
- // cas des hits ajax sur les inclusions ajax
- traiter_appels_inclusions_ajax()
- or
- // cas des formulaires charger/verifier/traiter
- traiter_formulaires_dynamiques()
- ) {
- exit;
- } // le hit est fini !
+ if (!autoriser_sans_cookie($exec)){
+ // Charger l'aiguilleur qui va mettre sur la bonne voie les traitements derogatoires
+ include_spip('public/aiguiller');
+ if (
+ // cas des appels actions ?action=xxx
+ traiter_appels_actions()
+ or
+ // cas des hits ajax sur les inclusions ajax
+ traiter_appels_inclusions_ajax()
+ or
+ // cas des formulaires charger/verifier/traiter
+ traiter_formulaires_dynamiques()
+ ){
+ exit;
+ } // le hit est fini !
+ }
}
// securiser les redirect du back-office
if (_request('redirect')) {
'pass_procedure_changer' => 'Pour modifier votre mot de passe, merci d’indiquer l’adresse email associée à votre compte.',
'pass_quitter_fenetre' => 'Quitter cette fenêtre',
'pass_rappel_login' => 'Rappel : votre identifiant (login) est « @login@ ».',
- 'pass_recevoir_mail' => 'Vous allez recevoir un email vous indiquant comment retrouver votre accès au site.',
+ 'pass_recevoir_mail' => 'Un lien de réinitialisation de votre mot de passe vous a été envoyé sur votre adresse email (si celle-ci est valide).',
'pass_retour_public' => 'Retour sur le site public',
'pass_rien_a_faire_ici' => 'Rien à faire ici.',
'pass_vousinscrire' => 'Vous inscrire sur ce site',
<paquet
prefix="spip"
categorie="outil"
- version="3.2.4"
+ version="3.2.5"
etat="stable"
compatibilite="];["
schema="23375"
}
// numerotons les occurrences d'un meme prefix
- $versions[$prefix] = $id = isset($versions[$prefix]) ? $versions[$prefix] + 1 : '';
+ $versions[$prefix] = $id = isset($versions[$prefix]) ? intval($versions[$prefix]) + 1 : '';
$class_li .= ($actif ? " actif" : "") . ($expose ? " on" : "");
// {par #ENV{X}} avec X absent de l'URL
// IN sur collection vide (ce dernier devrait pouvoir etre fait a la compil)
if ($where = &$this->command['where']) {
- $menage = false;
foreach ($where as $k => $v) {
if (is_array($v)) {
if ((count($v) >= 2) && ($v[0] == 'REGEXP') && ($v[2] == "'.*'")) {
}
if ((!$op) or ($op == 1) or ($op == '0=0')) {
unset($where[$k]);
- $menage = true;
}
// traiter {cle IN a,b} ou {valeur !IN a,b}
// prendre en compte le cas particulier de sous-requetes
if (preg_match(',^\(\(([\w/]+)(\s+NOT)?\s+IN\s+(\(.*\))\)(?:\s+(AND|OR)\s+\(([\w/]+)(\s+NOT)?\s+IN\s+(\(.*\))\))*\)$,',
$op, $regs)) {
$this->ajouter_filtre($regs[1], 'IN', strlen($req) ? $req : $regs[3], $regs[2]);
- unset($op);
+ unset($op, $where[$k]);
}
}
foreach ($where as $k => $v) {
CSSTidy is a CSS minifier
+* v1.6.5 :
+ fix warnings with PHP 7.3
* v1.6.4 :
preserve important comments (starting with !) in the minification /*! Credits/Licence */
* v1.6.3 :
* An online version should be available here: http://cdburnerxp.se/cssparse/css_optimiser.php
* @package csstidy
* @author Florian Schmitz (floele at gmail dot com) 2005-2006
- * @version 1.6.4
+ * @version 1.6.5
*/
class csstidy {
* @var string
* @access private
*/
- public $version = '1.6.4';
+ public $version = '1.6.5';
/**
* Stores the settings
* @var array
$this->str_char[] = $string{$i} === '(' ? ')' : $string{$i};
$this->from[] = 'instr';
$this->quoted_string[] = ($_str_char === ')' && $string{$i} !== '(' && trim($_cur_string)==='(')?$_quoted_string:!($string{$i} === '(');
- continue;
+ continue 2;
}
if ($_str_char !== ")" && ($string{$i} === "\n" || $string{$i} === "\r") && !($string{$i - 1} === '\\' && !$this->escaped($string, $i - 1))) {
<paquet
prefix="compresseur"
categorie="performance"
- version="1.12.8"
+ version="1.12.9"
etat="stable"
compatibilite="[3.2.0;3.2.*]"
logo="images/compresseur-32.png"
* @return string
*/
function dump_type_serveur() {
-
// chercher si sqlite2 ou 3 est disponible
include_spip('req/sqlite3');
- if (spip_versions_sqlite3()) {
+ if (function_exists('spip_versions_sqlite3') and spip_versions_sqlite3()) {
return 'sqlite3';
}
+ if (function_exists('spip_versions_sqlite3')) {
+ spip_log("ERREUR sqlite3 n'est pas correctement installé : "
+ ."extension_loaded('pdo')=".extension_loaded('pdo')
+ ." extension_loaded('pdo_sqlite')=".extension_loaded('pdo_sqlite'),
+ _LOG_ERREUR);
+ }
include_spip('req/sqlite2');
- if (spip_versions_sqlite2()) {
+ if (function_exists('spip_versions_sqlite2') and spip_versions_sqlite2()) {
return 'sqlite2';
}
<paquet
prefix="dump"
categorie="maintenance"
- version="1.8.4"
+ version="1.8.5"
etat="stable"
compatibilite="[3.2.0;3.2.*]"
logo="prive/themes/spip/images/base-backup-32.png"
<paquet
prefix="mots"
categorie="edition"
- version="2.8.6"
+ version="2.8.7"
etat="stable"
compatibilite="[3.2.0;3.2.*]"
logo="prive/themes/spip/images/mot-32.png"
<option value="x"> </option>
<BOUCLE_mots(MOTS){id_groupe}{par num titre, multi titre}>
#SET{value,mot-#ID_MOT-#OBJET-#ID_OBJET}
- <option value="#GET{value}"[(#GET{value}|=={#GET{expose}}|oui)selected="selected" class="on"]>#TITRE</option>
+ <option value="#GET{value}"[(#GET{value}|=={#GET{expose}}|oui)selected="selected" class="on"]>[(#RANG). ]#TITRE</option>
</BOUCLE_mots>
</select>
<input type="submit" class="submit" name="groupe#ID_GROUPE" value="<:bouton_changer:>"[(#GET{selected}|non)style="visibility:hidden;"]/>
<option value="x"> </option>
<BOUCLE_mots(MOTS){id_groupe}{id_mot !IN #ENV{exclus}}{par num titre, multi titre}>
#SET{value,mot-#ID_MOT-#OBJET-#ID_OBJET}
- <option value="#GET{value}"[(#GET{value}|=={#ENV{ajouter_lien}|table_valeur{groupe#ID_GROUPE}}|oui)selected="selected"#SET{selected,' '}]>#TITRE</option>
+ <option value="#GET{value}"[(#GET{value}|=={#ENV{ajouter_lien}|table_valeur{groupe#ID_GROUPE}}|oui)selected="selected"#SET{selected,' '}]>[(#RANG). ]#TITRE</option>
</BOUCLE_mots>
</select>
<input type="submit" class="submit" name="groupe#ID_GROUPE" value="<:bouton_ajouter:>"[(#GET{selected}|non)style="visibility:hidden;"]/>
trim(extraire_attribut($match[1], 'url')));
}
+ // GitHub : Identification du commit
+ if (preg_match(',<id>[^/]+/(\w+)</id>,Uims', $item, $regs)) {
+ $data['id_commit'] = $regs[1];
+ }
+
// tags
# a partir de "<dc:subject>", (del.icio.us)
# ou <media:category> (flickr)
<paquet
prefix="sites"
categorie="edition"
- version="1.10.3"
+ version="1.10.4"
etat="stable"
compatibilite="[3.2.0;3.2.*]"
logo="prive/themes/spip/images/site-32.png"
*
* @param string $nom Nom de la librairie
* @param string $source URL pour obtenir la librairie
+ * @return bool
*/
public function add_lib($nom, $source) {
if (!$this->decideur->est_presente_lib($nom)) {
* @see Actionneur::sauver_actions()
**/
public function get_actions() {
- lire_fichier(_DIR_TMP . 'stp_actions.txt', $contenu);
- $infos = unserialize($contenu);
- $this->end = $infos['todo'];
- $this->work = $infos['work'];
- $this->done = $infos['done'];
- $this->err = $infos['err'];
- $this->lock = $infos['lock'];
+ if (
+ lire_fichier(_DIR_TMP . 'stp_actions.txt', $contenu)
+ and $contenu
+ and $infos = unserialize($contenu)
+ and is_array($infos)
+ ) {
+ $this->end = $infos['todo'];
+ $this->work = $infos['work'];
+ $this->done = $infos['done'];
+ $this->err = $infos['err'];
+ $this->lock = $infos['lock'];
+ }
}
/**
* Remet tout à zéro pour pouvoir repartir d'un bon pied.
**/
public function nettoyer_actions() {
- $this->todo = array();
+ $this->end = array();
$this->done = array();
$this->work = array();
$this->err = array();
$bornes['max']['incluse'] = true;
}
// On les nettoie des suffixes d'etat
- $borne_inf = strtolower(preg_replace(',([0-9])[\s-.]?(dev|alpha|a|beta|b|rc|pl|p),i', '\\1',
+ $borne_inf = strtolower(preg_replace(',([0-9])[\s.-]?(dev|alpha|a|beta|b|rc|pl|p),i', '\\1',
$bornes['min']['valeur']));
- $borne_sup = strtolower(preg_replace(',([0-9])[\s-.]?(dev|alpha|a|beta|b|rc|pl|p),i', '\\1',
+ $borne_sup = strtolower(preg_replace(',([0-9])[\s.-]?(dev|alpha|a|beta|b|rc|pl|p),i', '\\1',
$bornes['max']['valeur']));
// On determine les branches inf et sup issues du phrasage de l'intervalle
$version_normalisee = '';
- if (preg_match(',([0-9.]+)[\s-.]?(dev|alpha|a|beta|b|rc|pl|p)?,i', $version, $matches)) {
+ if (preg_match(',([0-9.]+)[\s.-]?(dev|alpha|a|beta|b|rc|pl|p)?,i', $version, $matches)) {
if (isset($matches[1]) and $matches[1]) {
$v = explode('.', $matches[1]);
$vn = array();
/**
* Construit le WHERE d'une requête SQL de selection des plugins ou paquets
- * compatibles avec une version ou une branche de spip.
+ * compatibles avec une version, une branche de spip ou une liste de branches.
*
* Cette fonction est appelée par le critère {compatible_spip}
*
- * @used-by svp_compter()
* @used-by critere_compatible_spip_dist()
*
* @param string $version
- * Numéro de version de SPIP, tel que 2.0.8
+ * Numéro de version de SPIP, tel que 2.0.8 ou de branche tel que 3.1 ou une liste de branche '3.1,3.2'
* @param string $table
* Table d'application ou son alias SQL
* @param string $op
* @return string
* Expression where de la requête SQL
*/
-function inc_where_compatible_spip($version = '', $table, $op) {
+function inc_where_compatible_spip($version, $table, $op) {
- // le critere s'applique a une VERSION (1.9.2, 2.0.8, ...)
- if (count(explode('.', $version)) == 3) {
- $min = 'SUBSTRING_INDEX(' . $table . '.compatibilite_spip, \';\', 1)';
- $max = 'SUBSTRING_INDEX(' . $table . '.compatibilite_spip, \';\', -1)';
+ // En cas d'erreur sur le critère on annule l'effet du critère.
+ $where = '1=1';
- $where = 'CASE WHEN ' . $min . ' = \'\'
- OR ' . $min . ' = \'[\'
- THEN \'1.9.0\' <= \'' . $version . '\'
- ELSE TRIM(LEADING \'[\' FROM ' . $min . ') <= \'' . $version . '\'
- END
-AND
- CASE WHEN ' . $max . ' = \'\'
- OR ' . $max . ' = \']\'
- THEN \'99.99.99\' >= \'' . $version . '\'
- WHEN ' . $max . ' = \')\'
- OR ' . $max . ' = \'[\'
- THEN \'99.99.99\' > \'' . $version . '\'
- WHEN RIGHT(' . $max . ', 1) = \')\'
- OR RIGHT(' . $max . ', 1) = \'[\'
- THEN LEFT(' . $max . ', LENGTH(' . $max . ') - 1) > \'' . $version . '\'
- ELSE LEFT(' . $max . ', LENGTH(' . $max . ') - 1) >= \'' . $version . '\'
- END';
- } // le critere s'applique a une BRANCHE (1.9, 2.0, ...)
- elseif (count(explode('.', $version)) == 2) {
- $where = 'LOCATE(\'' . $version . '\', ' . $table . '.branches_spip) ' . $op . ' 0';
- } // le critere est vide ou mal specifie
- else {
- $where = '1=1';
- }
+ // On verifie en premier si on a affaire à une liste de branches ou à une version/branche unique.
+ if (strpos($version, ',') === false) {
+ // Le critère concerne une version ou une branche unique.
+ if (count(explode('.', $version)) == 3) {
+ // le critere s'applique a une version x.y.z (1.9.2, 2.0.8, ...)
+ $min = 'SUBSTRING_INDEX(' . $table . '.compatibilite_spip, \';\', 1)';
+ $max = 'SUBSTRING_INDEX(' . $table . '.compatibilite_spip, \';\', -1)';
+ $where = 'CASE WHEN ' . $min . ' = \'\'
+ OR ' . $min . ' = \'[\'
+ THEN \'1.9.0\' <= \'' . $version . '\'
+ ELSE TRIM(LEADING \'[\' FROM ' . $min . ') <= \'' . $version . '\'
+ END
+ AND
+ CASE WHEN ' . $max . ' = \'\'
+ OR ' . $max . ' = \']\'
+ THEN \'99.99.99\' >= \'' . $version . '\'
+ WHEN ' . $max . ' = \')\'
+ OR ' . $max . ' = \'[\'
+ THEN \'99.99.99\' > \'' . $version . '\'
+ WHEN RIGHT(' . $max . ', 1) = \')\'
+ OR RIGHT(' . $max . ', 1) = \'[\'
+ THEN LEFT(' . $max . ', LENGTH(' . $max . ') - 1) > \'' . $version . '\'
+ ELSE LEFT(' . $max . ', LENGTH(' . $max . ') - 1) >= \'' . $version . '\'
+ END';
+ } elseif (count(explode('.', $version)) == 2) {
+ // le critere s'applique a une branche x.y unique (par exemple 1.9)
+ $where = 'LOCATE(\'' . $version . '\', ' . $table . '.branches_spip) ' . $op . ' 0';
+ }
+ } else {
+ // Le critère concerne forcément une liste de branches (la liste n'est pas disponible pour une version).
+ $branches = explode(',', $version);
+ $where_liste = '';
+ foreach ($branches as $_branche) {
+ // On vérifie qu'on est bien en présence d'une branche.
+ if (count(explode('.', $_branche)) == 2) {
+ $where_liste .= ($where_liste ? ' AND ' : '') . 'LOCATE(\'' . $_branche . '\', ' . $table . '.branches_spip) ' . $op . ' 0';
+ }
+ }
+
+ // Si non vide, on renvoie le where calculé.
+ if ($where_liste) {
+ $where = $where_liste;
+ }
+ }
+
return $where;
}
<paquet
prefix="svp"
categorie="maintenance"
- version="1.3.8"
+ version="1.3.10"
etat="stable"
compatibilite="[3.2.0;3.2.*]"
logo="svp-64.png"
function svp_compter($entite, $id_depot = 0, $categorie = '', $compatible_spip = '') {
$compteurs = array();
- $group_by = array();
$where = array();
if ($id_depot) {
$where[] = "t1.id_depot=" . sql_quote($id_depot);
}
if ($entite == 'plugin') {
- $from = 'spip_plugins AS t2, spip_depots_plugins AS t1';
+ $from = array('spip_plugins AS t2', 'spip_depots_plugins AS t1');
$where[] = "t1.id_plugin=t2.id_plugin";
if ($categorie) {
$where[] = "t2.categorie=" . sql_quote($categorie);
$creer_where = charger_fonction('where_compatible_spip', 'inc');
$where[] = $creer_where($compatible_spip, 't2', '>');
}
- $compteurs['plugin'] = sql_count(sql_select('t2.id_plugin', $from, $where));
+ $compteurs['plugin'] = sql_count(sql_select('DISTINCT t1.id_plugin', $from, $where));
} elseif ($entite == 'paquet') {
+ $from = array('spip_paquets AS t1');
if ($categorie) {
$ids = sql_allfetsel('id_plugin', 'spip_plugins', 'categorie=' . sql_quote($categorie));
- $ids = array_map('reset', $ids);
+ $ids = array_column($ids, 'id_plugin');
$where[] = sql_in('t1.id_plugin', $ids);
}
if ($compatible_spip) {
$creer_where = charger_fonction('where_compatible_spip', 'inc');
$where[] = $creer_where($compatible_spip, 't1', '>');
}
- $compteurs['paquet'] = sql_countsel('spip_paquets AS t1', $where);
+ $compteurs['paquet'] = sql_countsel($from, $where);
} elseif ($entite == 'depot') {
- $champs = array(
+ $from = array('spip_depots AS t1');
+ $select = array(
'COUNT(t1.id_depot) AS depot',
'SUM(t1.nbr_plugins) AS plugin',
'SUM(t1.nbr_paquets) AS paquet',
'SUM(t1.nbr_autres) AS autre'
);
- $compteurs = sql_fetsel($champs, 'spip_depots AS t1', $where);
+ $compteurs = sql_fetsel($select, $from, $where);
} elseif ($entite == 'categorie') {
- $from = array('spip_plugins AS t2');
- $where_depot = $where[0];
- $where = array();
+ $from = array('spip_plugins AS t2', 'spip_depots_plugins AS t1');
+ $where[] = "t1.id_plugin=t2.id_plugin";
if ($id_depot) {
- $ids = sql_allfetsel('id_plugin', 'spip_depots_plugins AS t1', $where_depot);
- $ids = array_map('reset', $ids);
+ $ids = sql_allfetsel('id_plugin', 'spip_depots_plugins AS t1', $where);
+ $ids = array_column($ids, 'id_plugin');
$where[] = sql_in('t2.id_plugin', $ids);
}
if ($compatible_spip) {
}
if ($categorie) {
$where[] = "t2.categorie=" . sql_quote($categorie);
+ $compteurs['categorie'] = sql_count(sql_select('DISTINCT t1.id_plugin', $from, $where));
} else {
+ $select = array('t2.categorie', 'count(DISTINCT t1.id_plugin) as nb');
$group_by = array('t2.categorie');
+ $plugins = sql_allfetsel($select, $from, $where, $group_by);
+ $compteurs['categorie'] = array_column($plugins, 'nb', 'categorie');
}
- $compteurs['categorie'] = sql_countsel($from, $where, $group_by);
}
return $compteurs;
}
/**
- * Critère de compatibilité avec une version précise ou une branche de SPIP.
- *
- * Fonctionne sur les tables spip_paquets et spip_plugins
+ * Critère de compatibilité avec une version précise ou une branche de SPIP ou une liste de branches séparées par
+ * une virgule.
*
- * Si aucune valeur n'est explicité dans le critère, tous les enregistrements
- * sont retournés.
+ * Fonctionne sur les tables spip_paquets et spip_plugins.
+ * Si aucune valeur n'est explicité dans le critère on interroge le contexte pour trouver une variable
+ * compatible_spip et sinon tous les objets sont retournés.
*
- * Le ! (NOT) fonctionne sur le critère BRANCHE
+ * Le ! (NOT) ne fonctionne que sur une branche ou une liste de branches SPIP.
*
* @critere
* @example
* {compatible_spip 2.0.8} ou {compatible_spip 1.9}
* {compatible_spip #ENV{vers}} ou {compatible_spip #ENV{vers, 1.9.2}}
* {compatible_spip #GET{vers}} ou {compatible_spip #GET{vers, 2.1}}
+ * {compatible_spip '2.0,2.1'}
+ * {!compatible_spip 2.0}
+ * {!compatible_spip '2.0,2.1'}
+ * {!compatible_spip #ENV{vers}} ou {!compatible_spip #GET{vers}}
*
* @param string $idb Identifiant de la boucle
* @param array $boucles AST du squelette
* @param Critere $crit Paramètres du critère dans cette boucle
+ *
* @return void
*/
function critere_compatible_spip_dist($idb, &$boucles, $crit) {
+ // Initialisation de la table (spip_plugins ou spip_paquets)
$boucle = &$boucles[$idb];
$table = $boucle->id_table;
- // Si on utilise ! la fonction LOCATE doit retourner 0.
- // -> utilise uniquement avec le critere BRANCHE
+ // Initialisation du numéro de critère pour utiliser plusieurs fois le critère dans la même boucle
+ static $i = 1;
+
+ // La fonction LOCATE retourne soit 0 (pas trouvée) soit une valeur strictement supérieure à 0 (trouvée).
+ // Donc avec le modificateur not l'opérateur est un "=", sinon un ">".
+ // Le NOT s'utilise uniquement avec une branche SPIP (ex 2.0).
$op = ($crit->not == '!') ? '=' : '>';
+ // On calcule le code des critères.
+ // -- Initialisation avec le chargement de la fonction de calcul du critère.
$boucle->hash .= '
// COMPATIBILITE SPIP
$creer_where = charger_fonction(\'where_compatible_spip\', \'inc\');';
- // version/branche explicite dans l'appel du critere
- if (isset($crit->param[0][0])) {
- $version = calculer_liste(array($crit->param[0][0]), array(), $boucles, $boucle->id_parent);
- $boucle->hash .= '
- $where = $creer_where(' . $version . ', \'' . $table . '\', \'' . $op . '\');
- ';
- }
- // pas de version/branche explicite dans l'appel du critere
- // on regarde si elle est dans le contexte
- else {
+ // On traite le critère suivant que la version ou la branche est explicitement fournie ou pas.
+ if (!empty($crit->param)) {
+ // La ou les versions/branches sont explicites dans l'appel du critere.
+ // - on boucle sur les paramètres sachant qu'il est possible de fournir une liste séparée par une virgule
+ // (ex 3.2,3.1)
+ foreach ($crit->param as $_param) {
+ if (isset($_param[0])) {
+ $version = calculer_liste(array($_param[0]), array(), $boucles, $boucle->id_parent);
+ $boucle->hash .= '
+ $where' . $i . ' = $creer_where(' . $version . ', \'' . $table . '\', \'' . $op . '\');
+ ';
+ $boucle->where[] = '$where' . $i;
+ $i++;
+ }
+ }
+ } else {
+ // Pas de version ou de branche explicite dans l'appel du critere.
+ // - on regarde si elle est dans le contexte
$boucle->hash .= '
$version = isset($Pile[0][\'compatible_spip\']) ? $Pile[0][\'compatible_spip\'] : \'\';
- $where = $creer_where($version, \'' . $table . '\', \'' . $op . '\');
+ $where' . $i . ' = $creer_where($version, \'' . $table . '\', \'' . $op . '\');
';
+ $boucle->where[] = '$where' . $i;
+ $i++;
}
-
- $boucle->where[] = '$where';
}
/**
<paquet
prefix="urls"
categorie="statistique"
- version="2.1.7"
+ version="2.1.8"
etat="stable"
compatibilite="[3.2.0;3.2.*]"
logo="prive/themes/spip/images/url-32.png"
<a href="#"
title="Modifier l'URL"
onclick="jQuery(this).closest('.editer_urls').find('.edition').toggle('fast').closest('.editer_urls').delay(300).toggleClass('open');return false;"
- >]<span class="edit"><:bouton_modifier:></span><span class="url" id="url-#OBJET-#ID_OBJET">(#ID_OBJET|generer_url_entite{#OBJET,'','',#EVAL{true}}|url_absolue)</span>[(#GET{auth})</a>]</span>]
+ ><span class="edit"><:bouton_modifier:></span>]<span class="url" id="url-#OBJET-#ID_OBJET">(#ID_OBJET|generer_url_entite{#OBJET,'','',#EVAL{true}}|url_absolue)</span>[(#GET{auth})</a>]</span>]
[(#AUTORISER{modifier,#OBJET,#ID_OBJET})
<div class="edition">
<div class="ajax">
$login = strval(_request('var_login'));
}
// si on est deja identifie
+ if (!$login and isset($GLOBALS['visiteur_session']['email'])) {
+ $login = $GLOBALS['visiteur_session']['email'];
+ }
if (!$login and isset($GLOBALS['visiteur_session']['login'])) {
$login = $GLOBALS['visiteur_session']['login'];
}
} elseif ($erreur) {
// une erreur d'un SSO indique dans la redirection vers ici
// mais il faut se proteger de toute tentative d'injection malveilante
- include_spip('inc/texte');
- $valeurs['message_erreur'] = safehtml($erreur);
+ include_spip('inc/filtres');
+ $valeurs['message_erreur'] = textebrut($erreur);
}
return $valeurs;
#bando_haut ul.deroulant li ul.menu-2col { max-width: initial; -moz-column-count: 2; -moz-column-gap: 0; -webkit-column-count: 2; -webkit-column-gap: 0; -webkit-perspective:1; column-count: 2; column-gap: 0; }
#bando_haut ul.deroulant li.actif ul, #bando_haut ul.deroulant li.actif_tempo ul { #ENV{left}:auto;}
#bando_haut ul.deroulant li a { display: block; color:#444; font-weight:bold;}
+#bando_haut ul.deroulant li ul.menu-2col a {display: inline-block;}
#bando_haut ul.deroulant li ul li { background-color: #fff; }
#bando_haut ul.deroulant li ul li a { }
#bando_haut ul.deroulant li ul li a:hover,
#bando_haut ul.deroulant li ul li a:focus { background-color: #[(#ENV{claire}|couleur_eclaircir|couleur_eclaircir)]; }
+#bando_haut ul.deroulant li ul.menu-2col {background-color: #[(#ENV{claire}|couleur_eclaircir{.92})];}
+#bando_haut ul.deroulant li.favori { background-color: #fff; }
#bando_haut ul.deroulant li.non_favori { background-color: #[(#ENV{claire}|couleur_eclaircir{.92})]; }
#bando_haut ul.deroulant li.favori + li.non_favori { border-top:1px solid #aaa; }
<div class="page">
<INCLURE{fond=inclure/header} />
- <div class="nav clearfix" id="nav">
- <INCLURE{fond=inclure/nav,env} />
- </div>
+ <INCLURE{fond=inclure/nav,env} />
<div class="main">
<div class="wrapper">
. _T('info_message_2') . ' '
. $sujet;
$texte = _request('texte_message_auteur');
+ $texte .= "\n-- $adres";
$texte .= "\n\n-- " . _T('envoi_via_le_site') . ' '
. supprimer_tags(extraire_multi($GLOBALS['meta']['nom_site']))
. ' (' . $GLOBALS['meta']['adresse_site'] . "/) --\n";
$envoyer_mail = charger_fonction('envoyer_mail', 'inc');
- if ($envoyer_mail($mail, $sujet, $texte, $adres,
- 'X-Originating-IP: ' . $GLOBALS['ip'])) {
+ $corps = array(
+ 'texte' => $texte,
+ 'repondre_a' => $adres,
+ 'headers' => array(
+ "X-Originating-IP: " . $GLOBALS['ip'],
+ ),
+ );
+
+ if ($envoyer_mail($mail, $sujet, $corps)) {
$message = _T('form_prop_message_envoye');
return array('message_ok' => $message);
$res = array('message_erreur' => $err);
} else {
auteur_effacer_jeton($id_auteur);
- $login = $row['login'];
+
+ // Par défaut, on rappelle de s'identifier avec son email s'il existe
+ // et qu'il n'est PAS utilisé par quelqu'un d'autre
+ if (
+ $row['email']
+ and !sql_fetsel(
+ 'id_auteur',
+ 'spip_auteurs',
+ array(
+ '(email='.sql_quote($row['email']).' or login='.sql_quote($row['email']).')',
+ 'id_auteur != '.$id_auteur
+ ),
+ '', '', '0,1'
+ )
+ ) {
+ $identifiant = $row['email'];
+ }
+ // Sinon on dit d'utiliser le login
+ else {
+ $identifiant = $row['login'];
+ }
$res['message_ok'] = '<b>' . _T('pass_nouveau_enregistre') . '</b>' .
- '<br />' . _T('pass_rappel_login', array('login' => $login));
+ '<br />' . _T('pass_rappel_login', array('login' => $identifiant));
include_spip('inc/auth');
$row = sql_fetsel('*', 'spip_auteurs', 'id_auteur=' . intval($id_auteur));
<paquet
prefix="dist"
categorie="squelette"
- version="3.2.1"
+ version="3.2.3"
etat="stable"
compatibilite="[3.2.0;3.2.*]"
logo="icon/skel.png"
<svn_revision>
<text_version>
-Origine: svn://trac.rezo.net/spip/tags/spip-3.2.4
-Revision: 24285
-Dernier commit: 2019-04-08 14:28:14 +0200
+Origine: svn://trac.rezo.net/spip/tags/spip-3.2.5
+Revision: 24404
+Dernier commit: 2019-09-16 14:02:37 +0200
</text_version>
-<origine>svn://trac.rezo.net/spip/tags/spip-3.2.4</origine>
-<revision>24285</revision>
-<commit>2019-04-08 14:28:14 +0200 </commit>
+<origine>svn://trac.rezo.net/spip/tags/spip-3.2.5</origine>
+<revision>24404</revision>
+<commit>2019-09-16 14:02:37 +0200 </commit>
</svn_revision>
\ No newline at end of file